package com.yami.shop.mystery.common.listener;

import cn.hutool.core.util.IdUtil;
import cn.hutool.core.util.ObjectUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.yami.shop.bean.enums.AirdropRecordEnum;
import com.yami.shop.bean.event.AirDropSuccessEvent;
import com.yami.shop.bean.event.GrantEvent;
import com.yami.shop.bean.event.KtVerificationRightsEvent;
import com.yami.shop.bean.event.QualificationEvent;
import com.yami.shop.bean.model.ShopDetail;
import com.yami.shop.bean.model.UserAirdrop;
import com.yami.shop.bean.param.SendUserDropsParam;
import com.yami.shop.common.exception.YamiShopBindException;
import com.yami.shop.mystery.common.dao.MysteryBoxSkuMapper;
import com.yami.shop.mystery.common.model.MysteryBox;
import com.yami.shop.mystery.common.model.MysteryBoxOrder;
import com.yami.shop.mystery.common.model.MysteryBoxSku;
import com.yami.shop.mystery.common.model.MysteryBoxUserArk;
import com.yami.shop.mystery.common.service.MysteryBoxOpenRecordService;
import com.yami.shop.mystery.common.service.MysteryBoxService;
import com.yami.shop.mystery.common.service.MysteryBoxUserArkService;
import com.yami.shop.service.ChannelUserRelationRecordService;
import com.yami.shop.service.ShopDetailService;
import com.yami.shop.service.UserAirdropService;
import lombok.AllArgsConstructor;
import org.springframework.context.ApplicationEventPublisher;
import org.springframework.context.event.EventListener;
import org.springframework.stereotype.Component;
import org.springframework.transaction.annotation.Transactional;

import java.util.Date;

/**
 * 空投盲盒成功
 *
 * @author wxf
 * @date 2023/4/13 11:44
 */
@Component("boxDropListener")
@AllArgsConstructor
public class DropBoxListener {

    private final MysteryBoxUserArkService mysteryBoxUserArkService;

    private final MysteryBoxOpenRecordService mysteryBoxOpenRecordService;

    private final MysteryBoxSkuMapper boxSkuMapper;

    private final MysteryBoxService boxService;

    private final UserAirdropService userAirdropService;

    private final ChannelUserRelationRecordService channelUserRelationRecordService;

    private final ApplicationEventPublisher eventPublisher;

    private final ShopDetailService shopDetailService;


    /**
     * 空投盲盒
     *
     * @param event event
     */
    @EventListener(AirDropSuccessEvent.class)
    @Transactional
    public void boxDropListener(AirDropSuccessEvent event) {
        if (ObjectUtil.isEmpty(event.getDrops()) || event.getType() == AirdropRecordEnum.PROD.value() || event.getType() == AirdropRecordEnum.PROD_PRIORITY.value()) {
            return;
        }
        // ShopDetail shopDetail = shopDetailService.getShopDetailByShopId(event.getShopId());
        for (String userId : event.getUserIds()) {
            for (SendUserDropsParam drop : event.getDrops()) {
                Long boxId = drop.getTargetId();
                Integer boxNums = drop.getNums();
                MysteryBox byId = boxService.getById(boxId);
                UserAirdrop record = new UserAirdrop();
                record.setAirDropId(IdUtil.getSnowflakeNextId());
                record.setArticleName(byId.getBoxName());
                record.setArticleId(boxId.toString());
                record.setUserId(userId);
                record.setNum(boxNums);
                record.setArticleType(Integer.valueOf(drop.getType()));
                record.setBusinessType(event.getBusinessType());
                record.setCreateTime(new Date());
                record.setDropShopId(event.getShopId());
                record.setAirdropBusinessId(event.getAirdropBusinessId());
                // 空投盲盒
                if (drop.getType() == 1) {
                    // 获取当前库存
                    MysteryBoxSku mysteryBoxSku = boxSkuMapper.getByMysteryBoxId(boxId);
                    if (mysteryBoxSku == null || mysteryBoxSku.getStocks() <= 0 || mysteryBoxSku.getStocks() - boxNums < 0) {
                        // 库存不足
                        record.setStatus(AirdropRecordEnum.FAIL.value());
                        record.setReason("盲盒库存不足");
                        userAirdropService.save(record);
                        eventPublisher.publishEvent(new KtVerificationRightsEvent(1L,event.getAirdropBusinessId()));
                        throw new YamiShopBindException("盲盒库存不足，请重试！");
                    }
                    // 判断用户是否有链上地址的
                    // if (!channelUserRelationRecordService.isHasDTCAddress(userId, byId.getChain(), shopDetail.getChannelCode())) {
                    //     record.setStatus(AirdropRecordEnum.FAIL.value());
                    //     record.setReason("未查询到空投用户的链上地址");
                    //     userAirdropService.save(record);
                    //     continue;
                    // }
                    if (!boxService.decrMysteryBoxSkuStocks(boxId, boxNums)) {
                        record.setStatus(AirdropRecordEnum.FAIL.value());
                        record.setReason("更新盲盒库存失败");
                        userAirdropService.save(record);
                        eventPublisher.publishEvent(new KtVerificationRightsEvent(1L,event.getAirdropBusinessId()));
                        throw new YamiShopBindException("更新盲盒库存失败！");
                    }
                    // 增加开盒次数
                    MysteryBoxUserArk mysteryBoxUserArk = mysteryBoxUserArkService.getOne(Wrappers.lambdaQuery(MysteryBoxUserArk.class).eq(MysteryBoxUserArk::getUid, userId).eq(MysteryBoxUserArk::getBid, boxId));
                    if (ObjectUtil.isEmpty(mysteryBoxUserArk)) {
                        MysteryBoxUserArk userArk = new MysteryBoxUserArk();
                        userArk.setUid(userId);
                        userArk.setBid(boxId);
                        userArk.setCount(Long.valueOf(boxNums));
                        userArk.setStatus("0");
                        mysteryBoxUserArkService.save(userArk);
                    } else {
                        mysteryBoxUserArkService.update(Wrappers.lambdaUpdate(MysteryBoxUserArk.class).setSql("count = count + " + boxNums + ",status = 0").eq(MysteryBoxUserArk::getUid, userId).eq(MysteryBoxUserArk::getBid, boxId));
                    }
                    // 生成默认开合记录
                    MysteryBoxOrder mysteryBoxOrder = new MysteryBoxOrder();
                    mysteryBoxOrder.setMysteryBoxId(boxId);
                    mysteryBoxOrder.setUserId(userId);
                    mysteryBoxOrder.setProdCount(boxNums.longValue());
                    mysteryBoxOpenRecordService.initMysteryBoxOpenRecord(mysteryBoxOrder);
                }
                // 空投盲盒优先购资格
                if (drop.getType() == 3) {
                    eventPublisher.publishEvent(new QualificationEvent(userId, null, boxId, boxNums.longValue(), 1L, 2, record.getAirDropId().toString(), ObjectUtil.isNotNull(drop.getEffectiveTime()) ? drop.getEffectiveTime() : null));
                }
                record.setStatus(AirdropRecordEnum.SUCCESS.value());
                record.setSuccessNum(boxNums);
                userAirdropService.save(record);
            }
            // 空投权益券系统自动空投完成之后通知权益服务处理权益券状态
            if (ObjectUtil.isNotEmpty(event) && event.getBusinessType() == 3 && ObjectUtil.isNotNull(event.getAirdropBusinessId())) {
                eventPublisher.publishEvent(new KtVerificationRightsEvent(2L,event.getAirdropBusinessId()));
            }
            //  空投邀请、拉新奖励后通知上游服务，修改奖励发放状态
            if (ObjectUtil.isNotEmpty(event) && event.getBusinessType() == 4 && ObjectUtil.isNotNull(event.getAirdropBusinessId())) {
                eventPublisher.publishEvent(new GrantEvent(event.getAirdropBusinessId(),1));
            }
        }
    }
}
